package com.grouuu.layer;

import com.grouuu.asset.Asset;
import com.grouuu.geom.Rectangle;
import com.grouuu.world.World;
import js.Browser;
import js.html.CanvasElement;
import js.html.CanvasRenderingContext2D;
import js.html.Event;
import js.html.ImageData;
import js.html.ImageElement;
import js.html.Rect;

/**
 * ...
 * @author Grouuu
 */
class LayerGround
{
	private var bufferContext:CanvasRenderingContext2D;
	private var context:CanvasRenderingContext2D;
	private var asset:Asset;
	
	private var currentPosX:Int;
	private var currentPosY:Int;
	private var currentDecalX:Int;
	private var currentDecalY:Int;
	private var olderOriginTileX:Int = -1;
	private var olderOriginTileY:Int = -1;

	public function new(canvas:CanvasElement, asset:Asset) 
	{
		var bufferCanvas:CanvasElement = Browser.document.createCanvasElement();
		bufferCanvas.width = World.SCENE_W;
		bufferCanvas.height = World.SCENE_H;
		bufferContext = bufferCanvas.getContext2d();
		context = canvas.getContext2d();
		this.asset = asset;
		
		currentPosX = 0;
		currentPosY = 0;
	}
	
	public function init(originTileX:Int, originTileY:Int):Void
	{
		olderOriginTileX = originTileX;
		olderOriginTileY = originTileY;
		
		clear();
		
		var tileID:String;
		
		for (row in 0... World.NB_ROW)
		{
			for (col in 0... World.NB_COL)
				addTile(col, row, originTileX, originTileY);
		}
		
		render();
	}
	
	public function update(posOriginX:Int, posOriginY:Int):Void 
	{
		var originTileX:Int = Math.floor(posOriginX / World.TILE_W);
		var originTileY:Int = Math.floor(posOriginY / World.TILE_H);
		
		resetBuffer(originTileX, originTileY);
		//clear();
		
		currentDecalX = posOriginX % World.TILE_W;
		currentDecalY = posOriginY % World.TILE_H;
		
		var tx:Int;
		var ty:Int;
		
		if (originTileX > olderOriginTileX)
		{
			for (i in 0... World.NB_ROW + 2)
			{
				tx = World.NB_COL + 2;
				ty = i;
				
				addTile(tx, ty, originTileX, originTileY);
			}
		}
		else if(originTileX < olderOriginTileX)
		{
			for (i in 0... World.NB_ROW + 2)
			{
				tx = World.NB_COL;
				ty = i;
				
				addTile(tx, ty, originTileX, originTileY);
			}
		}
		
		olderOriginTileX = originTileX;
		olderOriginTileY = originTileY;
		
		render();
	}
	
	private function addTile(row:Int, col:Int, originTileX:Int, originTileY:Int):Void
	{
		var tileID:String = asset.mapData.getTileID(originTileX + row, originTileY + col);
		
		put(tileID, row * 32, col * 32);
	}
	
	private function put(tileID:String, posTileX:Int, posTileY:Int):Void
	{
		var tileRect:Rectangle = asset.mapData.getTileCoord(tileID);
		
		if (tileRect != null)
			bufferContext.drawImage(asset.mapImage, tileRect.x, tileRect.y, tileRect.width, tileRect.height, posTileX, posTileY, tileRect.width, tileRect.height);
	}
	
	private function render():Void
	{
		context.drawImage(bufferContext.canvas, 0, 0, World.SCENE_W, World.SCENE_H, 0, 0, World.SCENE_W, World.SCENE_H);
	}
	
	private function resetBuffer(originTileX:Int, originTileY:Int):Void
	{
		var oldOriginX:Int = (olderOriginTileX - originTileX) * World.TILE_W;
		var oldOriginY:Int = (olderOriginTileY - originTileY) * World.TILE_H;
		
		//trace(olderOriginTileX, olderOriginTileY, oldOriginX, oldOriginY);
		
		var img:ImageData = bufferContext.getImageData(0, 0, bufferContext.canvas.width, bufferContext.canvas.height); // trop gourmand (getImageData)
		
		bufferContext.clearRect(0, 0, bufferContext.canvas.width, bufferContext.canvas.height);
		
		bufferContext.drawImage(context.canvas, 0, 0, bufferContext.canvas.width, bufferContext.canvas.height, oldOriginX, oldOriginY, bufferContext.canvas.width, bufferContext.canvas.height);
	}
	
	private function clear():Void
	{
		context.clearRect(0, 0, context.canvas.width, context.canvas.height);
	}
}